using Godot;
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations.Schema;
using System.Linq;

public partial class NTileMap : TileMap
{
	static int TRANSPARENT_LAYER = 5;
	Dictionary<Vector2I, float> mT = new();
	Dictionary<Vector2I, int> mN = new Dictionary<Vector2I, int>();
	// Called when the node enters the scene tree for the first time.
	public override void _Ready()
	{
	}

	// Called every frame. 'delta' is the elapsed time since the previous frame.
	public override void _Process(double delta)
	{
		NCharacter cha = GetTree().GetFirstNodeInGroup(nameof(NCharacter)) as NCharacter;
		if (cha != null)
		{
			Vector2I c = LocalToMap(ToLocal(cha.GlobalPosition));
			if (GetCellSourceId(TRANSPARENT_LAYER, c) != -1)
			{
				//玩家位置有cell，需要透明效果
				_doNearbyTile(c);
			}
			else
			{
				//玩家位置没有cell，不需要透明效果
				foreach (var v in mT.Keys)
				{
					mT[v] = 1.0f;
				}
			}
			NotifyRuntimeTileDataUpdate(TRANSPARENT_LAYER);
		}
	}

	void _doNearbyTile(Vector2I i)
	{
		//清空下寻找标志位
		mN.Clear();
		_findNearbyTile(i);
	}

	void _findNearbyTile(Vector2I i)
	{
		//如果已经检查过了，直接跳过
		if (mN.ContainsKey(i))
			return;
		//设置已经检查过了
		mN.Add(i, 0);

		if (GetCellSourceId(TRANSPARENT_LAYER, i) != -1)
		{
			//如果有cell
			if (mT.ContainsKey(i))
				mT[i] = 0.3f;
			else
				mT.Add(i, 0.3f);

			//递归搜索周边的
			foreach (var v in GetSurroundingCells(i))
			{
				_findNearbyTile(v);
			}
		}
	}

	public override void _TileDataRuntimeUpdate(int layer, Vector2I coords, TileData tileData)
	{
		if (mT.ContainsKey(coords))
		{
			//透明值
			tileData.Modulate = new Color(1, 1, 1, mT[coords]);
			if (mT[coords] >= 1.0f)
			{
				mT.Remove(coords);
			}
		}
	}

	public override bool _UseTileDataRuntimeUpdate(int layer, Vector2I coords)
	{
		foreach (var v in mT)
		{
			if (layer == TRANSPARENT_LAYER && coords.X == v.Key.X && coords.Y == v.Key.Y)
			{
				return true;
			}
		}

		return false;
	}

	void _on_area_2d_body_entered(Node2D n)
	{

	}

	void _on_area_2d_body_exited(Node2D n)
	{

	}
}
